#pragma once

#include <cstddef>

/**
 * @brief 第三版本：支持裸指针构造与解引用访问。
 *
 * 关键新增：
 *   - 静态默认删除函数 `default_delete`。
 *   - 持有原始指针时的构造函数。
 *   - 解引用与箭头操作符。
 */
template <typename T, typename Deleter = void(*)(T*)>
class UniquePtr {
public:
    using pointer      = T*;
    using element_type = T;
    using deleter_type = Deleter;

    /// 默认删除行为：直接对指针执行 `delete`
    static void default_delete(T* ptr) noexcept {
        delete ptr;
    }

    constexpr UniquePtr() noexcept
        : ptr_(nullptr)
        , deleter_(default_delete) {}

    constexpr UniquePtr(std::nullptr_t) noexcept
        : UniquePtr() {}

    /**
     * @brief 以裸指针构造智能指针。
     *
     * @param ptr 外部通过 new 创建的对象指针。
     *            由 UniquePtr 接管所有权，后续会在析构或 reset 中释放。
     */
    explicit UniquePtr(pointer ptr) noexcept
        : ptr_(ptr)
        , deleter_(default_delete) {}

    pointer get() const noexcept {
        return ptr_;
    }

    /// 返回引用，用于解引用指针指向的对象
    element_type& operator*() const noexcept {
        return *ptr_;
    }

    /// 返回裸指针，便于访问成员函数
    pointer operator->() const noexcept {
        return ptr_;
    }

    explicit operator bool() const noexcept {
        return ptr_ != nullptr;
    }

private:
    pointer      ptr_;     ///< 当前托管的裸指针
    deleter_type deleter_; ///< 删除器对象，此处为函数指针，默认为 default_delete
};